package com.wontube.smr.web.controller.admin;

import java.io.File;
import java.io.FileOutputStream;
import java.util.Arrays;
import java.util.Comparator;
import java.util.List;
import java.util.UUID;

import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.servlet.ModelAndView;

import com.wontube.client.extension.utils.DateUtils;
import com.wontube.client.remote.Remoting;
import com.wontube.smr.web.client.admin.IAdminHomeBannerHandler;
import com.wontube.smr.web.client.model.po.HomeBanner;

/**
 * home banner controller
 * 
 * @author hewc@wondershare.cn
 * 
 */
@Controller
@RequestMapping(value = "/admin/homebanner", method = RequestMethod.GET)
public class AdminHomeBannerController {
	private final static String SUCCESS = "Done";
	private final static String FAILURE = "Failure: something wrong";

	@RequestMapping("")
	public ModelAndView website_home() {
		ModelAndView mv = new ModelAndView("admin/homebanner/homebanner_index");
		return mv;
	}

	@RequestMapping("/list")
	public ModelAndView list_website_links(@RequestParam(value = "sysId", required = false) String sysId,
			@RequestParam("countryCode") String countryCode,
			@RequestParam(value = "category", required = false) String category) {
		ModelAndView mv = new ModelAndView("admin/homebanner/website_list");
		IAdminHomeBannerHandler handler = getAdminHomeBannerHandler();
		List<HomeBanner> homeBanner = handler.listHomeBanner();
		mv.addObject("websiteList", homeBanner);
		return mv;
	}

	@RequestMapping("/get/{id}")
	public ModelAndView getWebsiteLink(@PathVariable("id") String id) {
		ModelAndView mv = new ModelAndView("admin/homebanner/update_website");
		IAdminHomeBannerHandler handler = getAdminHomeBannerHandler();
		HomeBanner website = handler.getHomeBannerByPK(id);
		mv.addObject("website", website);
		return mv;
	}

	@RequestMapping(value = "/update", method = RequestMethod.POST)
	@ResponseBody
	public String updateWebsiteLink(HomeBanner homeBanner) {
		IAdminHomeBannerHandler handler = getAdminHomeBannerHandler();
		homeBanner.setDescription("");
		homeBanner.setVersion(DateUtils.getNow());
		boolean success = handler.saveOrUpdateHomeBanner(homeBanner);
		if (success) {
			return SUCCESS;
		}
		return FAILURE;
	}

	@RequestMapping(value = "/add", method = RequestMethod.POST)
	@ResponseBody
	public String addWebsiteLink(HomeBanner homeBanner) {
		IAdminHomeBannerHandler handler = getAdminHomeBannerHandler();
		homeBanner.setId(UUID.randomUUID().toString());
		homeBanner.setVersion(DateUtils.getNow());
		homeBanner.setDescription("");
		boolean success = handler.saveOrUpdateHomeBanner(homeBanner);
		if (success) {
			return SUCCESS;
		}
		return FAILURE;
	}

	@RequestMapping("/delete/{id}")
	@ResponseBody
	public String deleteWebsiteLink(@PathVariable("id") String id) {
		IAdminHomeBannerHandler handler = getAdminHomeBannerHandler();
		boolean success = handler.deleteHomeBanner(id);
		if (success) {
			return SUCCESS;
		}
		return FAILURE;
	}

	@RequestMapping("/clean")
	@ResponseBody
	public String deleteCaches() {
		IAdminHomeBannerHandler handler = getAdminHomeBannerHandler();
		;
		if (handler.clearHomebannerCaches()) {
			return SUCCESS;
		} else {
			return FAILURE;
		}
	}

	private IAdminHomeBannerHandler getAdminHomeBannerHandler() {
		Remoting<IAdminHomeBannerHandler> remoting = new Remoting<IAdminHomeBannerHandler>();
		IAdminHomeBannerHandler handler = remoting.createService(IAdminHomeBannerHandler.class);
		return handler;
	}

	/**
	 * 
	 * @param uploadPath
	 * @return
	 */
	@RequestMapping("/upload")
	public ModelAndView upload(@Value("${uploadPath}") String uploadPath) {
		ModelAndView mv = new ModelAndView("admin/website/upload/upload_index");
		File dir = new File(uploadPath);
		File[] files = dir.listFiles();
		sortFiles(files);
		mv.addObject("files", files);
		mv.addObject("parent", "");
		return mv;
	}

	/**
	 * @param uploadPath
	 * @param dir
	 * @return
	 */
	@RequestMapping("/upload/unfold")
	public ModelAndView unfold(@Value("${uploadPath}") String uploadPath, @RequestParam("dir") String dir) {
		ModelAndView mv = new ModelAndView("admin/website/upload/unfold_file_list");
		File root = new File(uploadPath + dir);
		if (root.isDirectory()) {
			File[] files = root.listFiles();
			sortFiles(files);
			mv.addObject("parent", dir);
			mv.addObject("files", files);
		}

		return mv;
	}

	@RequestMapping(value = "/upload/delete", method = RequestMethod.POST)
	@ResponseBody
	public String delete_upload(@Value("${uploadPath}") String uploadPath, @RequestParam("dir") String dir) {
		File file = new File(uploadPath + dir);
		int aff = deleteFiles(file);
		return aff + "";
	}

	@RequestMapping(value = "/upload/mkdir", method = RequestMethod.POST)
	@ResponseBody
	public String mkdir(@Value("${uploadPath}") String uploadPath, @RequestParam("parent") String parent,
			@RequestParam("dir") String dir) {
		String[] dirs = dir.split("/");
		String path = uploadPath + parent;
		int aff = 0;
		for (String d : dirs) {
			if (!"".equals(d)) {
				path += "/" + d;
				File file = new File(path);
				if (!file.exists()) {
					if (file.mkdir()) {
						aff += 1;
					}
				}
			}
		}
		return aff + "";
	}

	@RequestMapping(value = "/upload/files", method = RequestMethod.POST)
	@ResponseBody
	public String upload_files(@Value("${uploadPath}") String uploadPath, @RequestParam("parent") String parent,
			@RequestParam("file") MultipartFile file) {
		String filename = file.getOriginalFilename();
		File tf = new File(uploadPath + parent + "/" + filename);
		if (tf.exists()) {
			return "Fail: File exists";
		} else {
			FileOutputStream fos = null;
			try {
				fos = new FileOutputStream(tf);
				fos.write(file.getBytes());
			} catch (Exception e) {
				return "Fail: error happen when write to file";
			} finally {
				if (fos != null) {
					try {
						fos.close();
					} catch (Exception e2) {
					}
				}
			}
		}
		return "Done";
	}

	private int deleteFiles(File file) {
		int aff = 0;
		if (file.isDirectory()) {
			File[] files = file.listFiles();
			if (files.length == 0) {
				if (file.delete()) {
					aff += 1;
				}
			} else {
				for (File file2 : files) {
					aff += deleteFiles(file2);
				}
				// delete youself
				if (file.delete()) {
					aff += 1;
				}
			}
		} else {
			if (file.delete()) {
				aff += 1;
			}
		}
		return aff;
	}

	private void sortFiles(File[] files) {
		Arrays.sort(files, new Comparator<File>() {
			@Override
			public int compare(File o1, File o2) {
				if (o1.isDirectory()) {
					if (!o2.isDirectory()) {
						return -1;
					}
				} else {
					if (o2.isDirectory()) {
						return 1;
					}
				}
				return 0;
			}
		});
	}
}
